/**
 * jquery.Jcrop.js v0.9.8
 * jQuery Image Cropping Plugin
 * @author Kelly Hallman <khallman@gmail.com>
 * Copyright (c) 2008-2009 Kelly Hallman - released under MIT License {{{
 *
 * Permission is hereby granted, free of charge, to any person
 * obtaining a copy of this software and associated documentation
 * files (the "Software"), to deal in the Software without
 * restriction, including without limitation the rights to use,
 * copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the
 * Software is furnished to do so, subject to the following
 * conditions:

 * The above copyright notice and this permission notice shall be
 * included in all copies or substantial portions of the Software.

 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 * OTHER DEALINGS IN THE SOFTWARE.

 * }}}
 */


 /*Modified by Cliff*/
 /* all changed are remarked by  'CHANGE TP ADOPT SINA PS' */
 /* PS related stuff:
    sometime we don't have 2nd image dimension
 */


// src_img : source image path
// src_img_dim : dimension of source image (widthxheight)
// crop_param(_in): current crop parameter (typicall saved inside PS)
// thumbnail_dim_in : bounding dimension for thumbnail if 'lock_ratio' is enabled
// default_thumbnail_dim: thumbnail size set by system
// thumbnail_fixed_size: correspond to 'image_size_fixed' setting in ps

// Some automation:
//   - set_default_crop_param(): set a default crop param if not provided
//     a default value will be given (center the crop)
//
//
//
//
//

// Its seems to be easier to write/debug when keep only a single 'flow of function'
//   new event added should be point to one of that function and continue that 'flow'
//
//   e.g. typical action like resize select area, change of thumbnail size will run :
//   1. setSelect([x1,y1,x2,y2])
//   2. updateCoords   ( which change crop param, zoom value)
//   3. ps_refresh_thumbnail
//   4. update_ui()    (which update ??
//
//
//
//
//



(function($) {

//$.Jcrop_SINAPS = function(obj,opt) //'CHANGE TP ADOPT SINA PS',
$.Jcrop_SINAPS = function(main_canvas, src_img, src_img_dim,
   crop_param_in, thumbnail_dim_in, default_thumbnail_dim,
   crop_param_html_id, thumbnail_html_id,
   thumbnail_fixed_size
   )
{
     // All Functions is defined within this block

      if (!src_img_dim){
        return error_msg("Image (size) does not exist!");
      }

      var src_img_prefix = src_img.substring(0,5);
      if (src_img_prefix != 'http:'){
        if (!src_img){
          return error_msg("Image (file) does not exist!");
        } else {
          src_img = "/"+src_img;
        }
      }
      // do some pre-requisite checking above.
      //

      var photo = src_img;
      
      var temp_size = src_img_dim.split(/x/);
      var photo_w =parseInt(temp_size[0]);
      var photo_h =parseInt(temp_size[1]);

      temp_size = thumbnail_dim_in.split(/x/);
      var thumbnail_w =parseInt(temp_size[0]);
      var thumbnail_h =parseInt(temp_size[1]);
      var curr_thumbnail_dim = thumbnail_dim_in;

      var crop_param = crop_param_in;

      if (crop_param_in == ""){
        //alert("no crop param is provided");
        crop_param = set_default_crop_param();
      }
      var loosen_lock_ratio = 0; // only lossen if crop param ratio no match with curr thumbnail ratio, (e.g. due to ps setting change)
      var lock_ratio  = set_default_lock_ratio_flag(); // lock aspect ratio of thumbnail, will affect the default value of the 'lock' checkbox
      var zoom        = set_default_zoom_value();    // real-only, for reference value
      
      //alert(" lock ratio flag: "+lock_ratio);
      create_ps_working_canvas();
      //alert( temp_pos[0] + " / " +temp_pos[1] + " vs " + thumbnail_w+ " / " +thumbnail_h);

  var opt={
    onchange: ps_refresh_thumbnail,
    onSelect: updateCoords,
    //aspectRatio: this.aspectRatio,
    //setSelect:   [ init_x1, init_y1, init_x2,  init_y2]
    setSelect: set_init_selection(crop_param)
  };

  var obj = $("#"+main_canvas+" .cropbox");
  // Sanitize some options {{{
  //var obj = obj, opt = opt; //'CHANGE TP ADOPT SINA PS', change constructor.

  //if (typeof(obj) !== 'object') obj = $(obj)[0];//'CHANGE TP ADOPT SINA PS',
  //if (typeof(opt) !== 'object') opt = { };

  // Some on-the-fly fixes for MSIE...sigh
  if (!('trackDocument' in opt))
  {
    opt.trackDocument = $.browser.msie ? false : true;
    if ($.browser.msie && $.browser.version.split('.')[0] == '8')
      opt.trackDocument = true;
  }

  if (!('keySupport' in opt))
      opt.keySupport = $.browser.msie ? false : true;

  // }}}
  // Extend the default options {{{
  var defaults = {

    // Basic Settings
    trackDocument:    false,
    baseClass:      'jcrop',
    addClass:     null,

    // Styling Options
    bgColor:      'black',
    bgOpacity:      .6,
    borderOpacity:    .4,
    handleOpacity:    .5,

    handlePad:      5,
    handleSize:     9,
    handleOffset:   5,
    edgeMargin:     14,

    aspectRatio:    0,
    keySupport:     true,
    cornerHandles:    true,
    sideHandles:    true,
    drawBorders:    true,
    dragEdges:      true,

    boxWidth:     0,
    boxHeight:      0,

    boundary:     8,
    animationDelay:   20,
    swingSpeed:     3,

    allowSelect:    true,
    allowMove:      true,
    allowResize:    true,

    minSelect:      [ 0, 0 ],
    maxSize:      [ 0, 0 ],
    minSize:      [ 0, 0 ],

    // Callbacks / Event Handlers
    onChange: function() { },
    onSelect: function() { }

  };
  var options = defaults;
  setOptions(opt);


  // }}}
  // Initialize some jQuery objects {{{

  var $origimg = $(obj);
  var $img = $origimg.clone().removeAttr('id').css({ position: 'absolute' });

  $img.width($origimg.width());
  $img.height($origimg.height());
  $origimg.after($img).hide();

  presize($img,options.boxWidth,options.boxHeight);

  var boundx = $img.width(),
    boundy = $img.height(),

    $div = $('<div />')
      .width(boundx).height(boundy)
      .addClass(cssClass('holder'))
      .css({
        position: 'relative',
        backgroundColor: options.bgColor
      }).insertAfter($origimg).append($img);
  ;

  if (options.addClass) $div.addClass(options.addClass);
  //$img.wrap($div);

  var $img2 = $('<img />')/*{{{*/
      .attr('src',$img.attr('src'))
      .css('position','absolute')
      .width(boundx).height(boundy)
  ;/*}}}*/
  var $img_holder = $('<div />')/*{{{*/
    .width(pct(100)).height(pct(100))
    .css({
      zIndex: 310,
      position: 'absolute',
      overflow: 'hidden'
    })
    .append($img2)
  ;/*}}}*/
  var $hdl_holder = $('<div />')/*{{{*/
    .width(pct(100)).height(pct(100))
    .css('zIndex',320);
  /*}}}*/
  var $sel = $('<div />')/*{{{*/
    .css({
      position: 'absolute',
      zIndex: 300
    })
    .insertBefore($img)
    .append($img_holder,$hdl_holder)
  ;/*}}}*/

  var bound = options.boundary;
  var $trk = newTracker().width(boundx+(bound*2)).height(boundy+(bound*2))
    .css({ position: 'absolute', top: px(-bound), left: px(-bound), zIndex: 290 })
    .mousedown(newSelection);

  /* }}} */
  // Set more variables {{{

  var xlimit, ylimit, xmin, ymin;
  var xscale, yscale, enabled = true;
  var docOffset = getPos($img),
    // Internal states
    btndown, lastcurs, dimmed, animating,
    shift_down;

  // }}}


    // }}}
  // Internal Modules {{{

  var Coords = function()/*{{{*/
  {
    var x1 = 0, y1 = 0, x2 = 0, y2 = 0, ox, oy;

    function setPressed(pos)/*{{{*/
    {
      var pos = rebound(pos);
      x2 = x1 = pos[0];
      y2 = y1 = pos[1];
    };
    /*}}}*/
    function setCurrent(pos)/*{{{*/
    {

      var pos = rebound(pos);
      ox = pos[0] - x2;
      oy = pos[1] - y2;

      x2 = pos[0];
      y2 = pos[1];

    };
    /*}}}*/
    function getOffset()/*{{{*/
    {
      return [ ox, oy ];
    };
    /*}}}*/
    function moveOffset(offset)/*{{{*/
    {
      var ox = offset[0], oy = offset[1];

      if (0 > x1 + ox) ox -= ox + x1;
      if (0 > y1 + oy) oy -= oy + y1;

      if (boundy < y2 + oy) oy += boundy - (y2 + oy);
      if (boundx < x2 + ox) ox += boundx - (x2 + ox);

      x1 += ox;
      x2 += ox;
      y1 += oy;
      y2 += oy;
    };
    /*}}}*/
    function getCorner(ord)/*{{{*/
    {
      var c = getFixed();
      switch(ord)
      {
        case 'ne': return [ c.x2, c.y ];
        case 'nw': return [ c.x, c.y ];
        case 'se': return [ c.x2, c.y2 ];
        case 'sw': return [ c.x, c.y2 ];
      }
    };
    /*}}}*/
    function getFixed()/*{{{*/
    {

      if (!options.aspectRatio) return getRect();


      // This function could use some optimization I think...
      var aspect = options.aspectRatio,
        min_x = options.minSize[0]/xscale,
        min_y = options.minSize[1]/yscale,
        max_x = options.maxSize[0]/xscale,
        max_y = options.maxSize[1]/yscale,
        rw = x2 - x1,
        rh = y2 - y1,
        rwa = Math.abs(rw),
        rha = Math.abs(rh),
        real_ratio = rwa / rha,
        xx, yy
      ;

      if (max_x == 0) { max_x = boundx * 10 }
      if (max_y == 0) { max_y = boundy * 10 }
      
      if (real_ratio < aspect)
      {
        yy = y2;
        var w = rha * aspect;  // CHANGE TP ADOPT SINA PS: added var w by cliff on 2009-11-10 14:25
        xx = rw < 0 ? x1 - w : w + x1;

        if (xx < 0)
        {
          xx = 0;
          h = Math.abs((xx - x1) / aspect);
          yy = rh < 0 ? y1 - h: h + y1;
        }
        else if (xx > boundx)
        {
          xx = boundx;
          h = Math.abs((xx - x1) / aspect);
          yy = rh < 0 ? y1 - h : h + y1;
        }
      }
      else
      {
        xx = x2;
        var h = rwa / aspect;  // CHANGE TP ADOPT SINA PS: added var h by cliff on 2009-11-10 14:25
        yy = rh < 0 ? y1 - h : y1 + h;
        if (yy < 0)
        {
          yy = 0;
          w = Math.abs((yy - y1) * aspect);
          xx = rw < 0 ? x1 - w : w + x1;
        }
        else if (yy > boundy)
        {
          yy = boundy;
          w = Math.abs(yy - y1) * aspect;
          xx = rw < 0 ? x1 - w : w + x1;
        }
      }

      // Magic %-)
      if(xx > x1) { // right side
        if(xx - x1 < min_x) {
        xx = x1 + min_x;
        } else if (xx - x1 > max_x) {
        xx = x1 + max_x;
        }
        if(yy > y1) {
        yy = y1 + (xx - x1)/aspect;
        } else {
        yy = y1 - (xx - x1)/aspect;
        }
      } else if (xx < x1) { // left side
        if(x1 - xx < min_x) {
        xx = x1 - min_x
        } else if (x1 - xx > max_x) {
        xx = x1 - max_x;
        }
        if(yy > y1) {
        yy = y1 + (x1 - xx)/aspect;
        } else {
        yy = y1 - (x1 - xx)/aspect;
        }
      }

      if(xx < 0) {
        x1 -= xx;
        xx = 0;
      } else  if (xx > boundx) {
        x1 -= xx - boundx;
        xx = boundx;
      }

      if(yy < 0) {
        y1 -= yy;
        yy = 0;
      } else  if (yy > boundy) {
        y1 -= yy - boundy;
        yy = boundy;
      }

      return last = makeObj(flipCoords(x1,y1,xx,yy));
    };
    /*}}}*/
    function rebound(p)/*{{{*/
    {

      if (p[0] < 0) p[0] = 0;
      if (p[1] < 0) p[1] = 0;

      if (p[0] > boundx) { p[0] = boundx; }
      if (p[1] > boundy) { p[1] = boundy; }

      return [ p[0], p[1] ];
    };
    /*}}}*/
    function flipCoords(x1,y1,x2,y2)/*{{{*/
    {
      var xa = x1, xb = x2, ya = y1, yb = y2;
      if (x2 < x1)
      {
        xa = x2;
        xb = x1;
      }
      if (y2 < y1)
      {
        ya = y2;
        yb = y1;
      }
      return [ Math.round(xa), Math.round(ya), Math.round(xb), Math.round(yb) ];
    };
    /*}}}*/
    function getRect()/*{{{*/
    {
      var xsize = x2 - x1;
      var ysize = y2 - y1;

      if (xlimit && (Math.abs(xsize) > xlimit))
        x2 = (xsize > 0) ? (x1 + xlimit) : (x1 - xlimit);
      if (ylimit && (Math.abs(ysize) > ylimit))
        y2 = (ysize > 0) ? (y1 + ylimit) : (y1 - ylimit);

      if (ymin && (Math.abs(ysize) < ymin))
        y2 = (ysize > 0) ? (y1 + ymin) : (y1 - ymin);
      if (xmin && (Math.abs(xsize) < xmin))
        x2 = (xsize > 0) ? (x1 + xmin) : (x1 - xmin);

      if (x1 < 0) { x2 -= x1; x1 -= x1; }
      if (y1 < 0) { y2 -= y1; y1 -= y1; }
      if (x2 < 0) { x1 -= x2; x2 -= x2; }
      if (y2 < 0) { y1 -= y2; y2 -= y2; }
      if (x2 > boundx) { var delta = x2 - boundx; x1 -= delta; x2 -= delta; }
      if (y2 > boundy) { var delta = y2 - boundy; y1 -= delta; y2 -= delta; }
      if (x1 > boundx) { var delta = x1 - boundy; y2 -= delta; y1 -= delta; }
      if (y1 > boundy) { var delta = y1 - boundy; y2 -= delta; y1 -= delta; }

      return makeObj(flipCoords(x1,y1,x2,y2));
    };
    /*}}}*/
    function makeObj(a)/*{{{*/
    {
      return { x: a[0], y: a[1], x2: a[2], y2: a[3],
        w: a[2] - a[0], h: a[3] - a[1] };
    };
    /*}}}*/

    return {
      flipCoords: flipCoords,
      setPressed: setPressed,
      setCurrent: setCurrent,
      getOffset: getOffset,
      moveOffset: moveOffset,
      getCorner: getCorner,
      getFixed: getFixed
    };
  }();

  /*}}}*/
  var Selection = function()/*{{{*/
  {
    var start, end, dragmode, awake, hdep = 370;
    var borders = { };
    var handle = { };
    var seehandles = false;
    var hhs = options.handleOffset;

    /* Insert draggable elements {{{*/

    // Insert border divs for outline
    if (options.drawBorders) {
      borders = {
          top: insertBorder('hline')
            .css('top',$.browser.msie?px(-1):px(0)),
          bottom: insertBorder('hline'),
          left: insertBorder('vline'),
          right: insertBorder('vline')
      };
    }

    // Insert handles on edges
    if (options.dragEdges) {
      handle.t = insertDragbar('n');
      handle.b = insertDragbar('s');
      handle.r = insertDragbar('e');
      handle.l = insertDragbar('w');
    }

    // Insert side handles
    options.sideHandles &&
      createHandles(['n','s','e','w']);

    // Insert corner handles
    options.cornerHandles &&
      createHandles(['sw','nw','ne','se']);

    /*}}}*/
    // Private Methods
    function insertBorder(type)/*{{{*/
    {
      var jq = $('<div />')
        .css({position: 'absolute', opacity: options.borderOpacity })
        .addClass(cssClass(type));
      $img_holder.append(jq);
      return jq;
    };
    /*}}}*/
    function dragDiv(ord,zi)/*{{{*/
    {
      var jq = $('<div />')
        .mousedown(createDragger(ord))
        .css({
          cursor: ord+'-resize',
          position: 'absolute',
          zIndex: zi
        })
      ;
      $hdl_holder.append(jq);
      return jq;
    };
    /*}}}*/
    function insertHandle(ord)/*{{{*/
    {
      return dragDiv(ord,hdep++)
        .css({ top: px(-hhs+1), left: px(-hhs+1), opacity: options.handleOpacity })
        .addClass(cssClass('handle'));
    };
    /*}}}*/
    function insertDragbar(ord)/*{{{*/
    {
      var s = options.handleSize,
        o = hhs,
        h = s, w = s,
        t = o, l = o;

      switch(ord)
      {
        case 'n': case 's': w = pct(100); break;
        case 'e': case 'w': h = pct(100); break;
      }

      return dragDiv(ord,hdep++).width(w).height(h)
        .css({ top: px(-t+1), left: px(-l+1)});
    };
    /*}}}*/
    function createHandles(li)/*{{{*/
    {
      for(i in li) handle[li[i]] = insertHandle(li[i]);
    };
    /*}}}*/
    function moveHandles(c)/*{{{*/
    {
      var midvert  = Math.round((c.h / 2) - hhs),
        midhoriz = Math.round((c.w / 2) - hhs),
        north = west = -hhs+1,
        east = c.w - hhs,
        south = c.h - hhs,
        x, y;

      'e' in handle &&
        handle.e.css({ top: px(midvert), left: px(east) }) &&
        handle.w.css({ top: px(midvert) }) &&
        handle.s.css({ top: px(south), left: px(midhoriz) }) &&
        handle.n.css({ left: px(midhoriz) });

      'ne' in handle &&
        handle.ne.css({ left: px(east) }) &&
        handle.se.css({ top: px(south), left: px(east) }) &&
        handle.sw.css({ top: px(south) });

      'b' in handle &&
        handle.b.css({ top: px(south) }) &&
        handle.r.css({ left: px(east) });
    };
    /*}}}*/
    function moveto(x,y)/*{{{*/
    {
      $img2.css({ top: px(-y), left: px(-x) });
      $sel.css({ top: px(y), left: px(x) });
    };
    /*}}}*/
    function resize(w,h)/*{{{*/
    {
      $sel.width(w).height(h);
    };
    /*}}}*/
    function refresh()/*{{{*/
    {
      var c = Coords.getFixed();

      Coords.setPressed([c.x,c.y]);
      Coords.setCurrent([c.x2,c.y2]);

      updateVisible();
    };
    /*}}}*/

    // Internal Methods
    function updateVisible()/*{{{*/
      { if (awake) return update(); };
    /*}}}*/
    function update()/*{{{*/
    {
      var c = Coords.getFixed();

      //alert("cx "+c.x+' cy '+c.y);

      resize(c.w,c.h);
      moveto(c.x,c.y);

      options.drawBorders &&
        borders['right'].css({ left: px(c.w-1) }) &&
          borders['bottom'].css({ top: px(c.h-1) });

      seehandles && moveHandles(c);
      awake || show();

      //'CHANGE TP ADOPT SINA PS',
      //options.onChange(unscale(c)); //remark by cliff
      ps_refresh_thumbnail(unscale(c));  // added by cliff

    };
    /*}}}*/
    function show()/*{{{*/
    {
      $sel.show();
      $img.css('opacity',options.bgOpacity);
      awake = true;
    };
    /*}}}*/
    function release()/*{{{*/
    {
      disableHandles();
      $sel.hide();
      $img.css('opacity',1);
      awake = false;
    };
    /*}}}*/
    function showHandles()//{{{
    {
      if (seehandles)
      {
        moveHandles(Coords.getFixed());
        $hdl_holder.show();
      }
    };
    //}}}
    function enableHandles()/*{{{*/
    {
      seehandles = true;
      if (options.allowResize)
      {
        moveHandles(Coords.getFixed());
        $hdl_holder.show();
        return true;
      }
    };
    /*}}}*/
    function disableHandles()/*{{{*/
    {
      seehandles = false;
      $hdl_holder.hide();
    };
    /*}}}*/
    function animMode(v)/*{{{*/
    {
      (animating = v) ? disableHandles(): enableHandles();
    };
    /*}}}*/
    function done()/*{{{*/
    {
      animMode(false);
      refresh();
    };
    /*}}}*/

    var $track = newTracker().mousedown(createDragger('move'))
        .css({ cursor: 'move', position: 'absolute', zIndex: 360 })

    $img_holder.append($track);
    disableHandles();

    return {
      updateVisible: updateVisible,
      update: update,
      release: release,
      refresh: refresh,
      setCursor: function (cursor) { $track.css('cursor',cursor); },
      enableHandles: enableHandles,
      enableOnly: function() { seehandles = true; },
      showHandles: showHandles,
      disableHandles: disableHandles,
      animMode: animMode,
      done: done
    };
  }();
  /*}}}*/
  var Tracker = function()/*{{{*/
  {
    var onMove    = function() { },
      onDone    = function() { },
      trackDoc  = options.trackDocument;

    if (!trackDoc)
    {
      $trk
        .mousemove(trackMove)
        .mouseup(trackUp)
        .mouseout(trackUp)
      ;
    }

    function toFront()/*{{{*/
    {
      $trk.css({zIndex:450});
      if (trackDoc)
      {
        $(document)
          .mousemove(trackMove)
          .mouseup(trackUp)
        ;
      }
    }
    /*}}}*/
    function toBack()/*{{{*/
    {
      $trk.css({zIndex:290});
      if (trackDoc)
      {
        $(document)
          .unbind('mousemove',trackMove)
          .unbind('mouseup',trackUp)
        ;
      }
    }
    /*}}}*/
    function trackMove(e)/*{{{*/
    {
      onMove(mouseAbs(e));
    };
    /*}}}*/
    function trackUp(e)/*{{{*/
    {
      e.preventDefault();
      e.stopPropagation();

      if (btndown)
      {
        btndown = false;

        onDone(mouseAbs(e));

        //'CHANGE TP ADOPT SINA PS'
        //options.onSelect(unscale(Coords.getFixed()));
        updateCoords(unscale(Coords.getFixed()));

        toBack();
        onMove = function() { };
        onDone = function() { };
      }

      return false;
    };
    /*}}}*/

    function activateHandlers(move,done)/* {{{ */
    {
      btndown = true;
      onMove = move;
      onDone = done;
      toFront();
      return false;
    };
    /* }}} */

    function setCursor(t) { $trk.css('cursor',t); };

    $img.before($trk);
    return {
      activateHandlers: activateHandlers,
      setCursor: setCursor
    };
  }();
  /*}}}*/
  var KeyManager = function()/*{{{*/
  {
    var $keymgr = $('<input type="radio" />')
        .css({ position: 'absolute', left: '-30px' })
        .keypress(parseKey)
        .blur(onBlur),

      $keywrap = $('<div />')
        .css({
          position: 'absolute',
          overflow: 'hidden'
        })
        .append($keymgr)
    ;

    function watchKeys()/*{{{*/
    {
      if (options.keySupport)
      {
        $keymgr.show();
        $keymgr.focus();
      }
    };
    /*}}}*/
    function onBlur(e)/*{{{*/
    {
      $keymgr.hide();
    };
    /*}}}*/
    function doNudge(e,x,y)/*{{{*/
    {
      if (options.allowMove) {
        Coords.moveOffset([x,y]);
        Selection.updateVisible();
      };
      e.preventDefault();
      e.stopPropagation();
    };
    /*}}}*/
    function parseKey(e)/*{{{*/
    {
      if (e.ctrlKey) return true;
      shift_down = e.shiftKey ? true : false;
      var nudge = shift_down ? 10 : 1;
      switch(e.keyCode)
      {
        case 37: doNudge(e,-nudge,0); break;
        case 39: doNudge(e,nudge,0); break;
        case 38: doNudge(e,0,-nudge); break;
        case 40: doNudge(e,0,nudge); break;

        case 27: Selection.release(); break;

        case 9: return true;
      }

      return nothing(e);
    };
    /*}}}*/

    if (options.keySupport) $keywrap.insertBefore($img);
    return {
      watchKeys: watchKeys
    };
  }();
  /*}}}*/

  // }}}
  // Internal Methods {{{

  function px(n) { return '' + parseInt(n) + 'px'; };
  function pct(n) { return '' + parseInt(n) + '%'; };
  function cssClass(cl) { return options.baseClass + '-' + cl; };
  function getPos(obj)/*{{{*/
  {
    // Updated in v0.9.4 to use built-in dimensions plugin
    var pos = $(obj).offset();
    return [ pos.left, pos.top ];
  };
  /*}}}*/
  function mouseAbs(e)/*{{{*/
  {
    return [ (e.pageX - docOffset[0]), (e.pageY - docOffset[1]) ];
  };
  /*}}}*/
  function myCursor(type)/*{{{*/
  {
    if (type != lastcurs)
    {
      Tracker.setCursor(type);
      //Handles.xsetCursor(type);
      lastcurs = type;
    }
  };
  /*}}}*/
  function startDragMode(mode,pos)/*{{{*/
  {
    docOffset = getPos($img);
    Tracker.setCursor(mode=='move'?mode:mode+'-resize');

    if (mode == 'move')
      return Tracker.activateHandlers(createMover(pos), doneSelect);

    var fc = Coords.getFixed();
    var opp = oppLockCorner(mode);
    var opc = Coords.getCorner(oppLockCorner(opp));

    Coords.setPressed(Coords.getCorner(opp));
    Coords.setCurrent(opc);

    Tracker.activateHandlers(dragmodeHandler(mode,fc),doneSelect);
  };
  /*}}}*/
  function dragmodeHandler(mode,f)/*{{{*/
  {
    return function(pos) {
      if (!options.aspectRatio) switch(mode)
      {
        case 'e': pos[1] = f.y2; break;
        case 'w': pos[1] = f.y2; break;
        case 'n': pos[0] = f.x2; break;
        case 's': pos[0] = f.x2; break;
      }
      else switch(mode)
      {
        case 'e': pos[1] = f.y+1; break;
        case 'w': pos[1] = f.y+1; break;
        case 'n': pos[0] = f.x+1; break;
        case 's': pos[0] = f.x+1; break;
      }
      Coords.setCurrent(pos);
      Selection.update();
    };
  };
  /*}}}*/
  function createMover(pos)/*{{{*/
  {
    var lloc = pos;
    KeyManager.watchKeys();

    return function(pos)
    {
      Coords.moveOffset([pos[0] - lloc[0], pos[1] - lloc[1]]);
      lloc = pos;

      Selection.update();
    };
  };
  /*}}}*/
  function oppLockCorner(ord)/*{{{*/
  {
    switch(ord)
    {
      case 'n': return 'sw';
      case 's': return 'nw';
      case 'e': return 'nw';
      case 'w': return 'ne';
      case 'ne': return 'sw';
      case 'nw': return 'se';
      case 'se': return 'nw';
      case 'sw': return 'ne';
    };
  };
  /*}}}*/
  function createDragger(ord)/*{{{*/
  {
    return function(e) {
      if (options.disabled) return false;
      if ((ord == 'move') && !options.allowMove) return false;
      btndown = true;
      startDragMode(ord,mouseAbs(e));
      e.stopPropagation();
      e.preventDefault();
      return false;
    };
  };
  /*}}}*/
  function presize($obj,w,h)/*{{{*/
  {
    var nw = $obj.width(), nh = $obj.height();
    if ((nw > w) && w > 0)
    {
      nw = w;
      nh = (w/$obj.width()) * $obj.height();
    }
    if ((nh > h) && h > 0)
    {
      nh = h;
      nw = (h/$obj.height()) * $obj.width();
    }
    xscale = $obj.width() / nw;
    yscale = $obj.height() / nh;
    $obj.width(nw).height(nh);
  };
  /*}}}*/
  function unscale(c)/*{{{*/
  {
    return {
      x: parseInt(c.x * xscale), y: parseInt(c.y * yscale),
      x2: parseInt(c.x2 * xscale), y2: parseInt(c.y2 * yscale),
      w: parseInt(c.w * xscale), h: parseInt(c.h * yscale)
    };
  };
  /*}}}*/
  function doneSelect(pos)/*{{{*/
  {
    var c = Coords.getFixed();
    if (c.w > options.minSelect[0] && c.h > options.minSelect[1])
    {
      Selection.enableHandles();
      Selection.done();
    }
    else
    {
      Selection.release();
    }
    Tracker.setCursor( options.allowSelect?'crosshair':'default' );
  };
  /*}}}*/
  function newSelection(e)/*{{{*/
  {
    if (options.disabled) return false;
    if (!options.allowSelect) return false;
    btndown = true;
    docOffset = getPos($img);
    Selection.disableHandles();
    myCursor('crosshair');
    var pos = mouseAbs(e);
    Coords.setPressed(pos);
    Tracker.activateHandlers(selectDrag,doneSelect);
    KeyManager.watchKeys();
    Selection.update();

    e.stopPropagation();
    e.preventDefault();
    return false;
  };
  /*}}}*/
  function selectDrag(pos)/*{{{*/
  {
    Coords.setCurrent(pos);
    Selection.update();
  };
  /*}}}*/
  function newTracker()
  {
    var trk = $('<div></div>').addClass(cssClass('tracker'));
    $.browser.msie && trk.css({ opacity: 0, backgroundColor: 'white' });
    return trk;
  };

  // }}}
  // API methods {{{

  function animateTo(a)/*{{{*/
  {
    var x1 = a[0] / xscale,
      y1 = a[1] / yscale,
      x2 = a[2] / xscale,
      y2 = a[3] / yscale;

    if (animating) return;

    var animto = Coords.flipCoords(x1,y1,x2,y2);
    var c = Coords.getFixed();
    var animat = initcr = [ c.x, c.y, c.x2, c.y2 ];
    var interv = options.animationDelay;

    var x = animat[0];
    var y = animat[1];
    var x2 = animat[2];
    var y2 = animat[3];
    var ix1 = animto[0] - initcr[0];
    var iy1 = animto[1] - initcr[1];
    var ix2 = animto[2] - initcr[2];
    var iy2 = animto[3] - initcr[3];
    var pcent = 0;
    var velocity = options.swingSpeed;

    Selection.animMode(true);

    var animator = function()
    {
      return function()
      {
        pcent += (100 - pcent) / velocity;

        animat[0] = x + ((pcent / 100) * ix1);
        animat[1] = y + ((pcent / 100) * iy1);
        animat[2] = x2 + ((pcent / 100) * ix2);
        animat[3] = y2 + ((pcent / 100) * iy2);

        if (pcent < 100) animateStart();
          else Selection.done();

        if (pcent >= 99.8) pcent = 100;

        setSelectRaw(animat);
      };
    }();

    function animateStart()
      { window.setTimeout(animator,interv); };

    animateStart();
  };
  /*}}}*/
  function setSelect(rect)//{{{
  {
    setSelectRaw([rect[0]/xscale,rect[1]/yscale,rect[2]/xscale,rect[3]/yscale]);

  };
  //}}}
  function setSelectRaw(l) /*{{{*/
  {
    Coords.setPressed([l[0],l[1]]);
    Coords.setCurrent([l[2],l[3]]);

    Selection.update();
  };
  /*}}}*/
  function setOptions(opt)/*{{{*/
  {
    if (typeof(opt) != 'object') opt = { };
    options = $.extend(options,opt);

    if (typeof(options.onChange)!=='function')
      options.onChange = function() { };

    if (typeof(options.onSelect)!=='function')
      options.onSelect = function() { };

  };
  /*}}}*/
  function tellSelect()/*{{{*/
  {
    return unscale(Coords.getFixed());
  };
  /*}}}*/
  function tellScaled()/*{{{*/
  {
    return Coords.getFixed();
  };
  /*}}}*/
  function setOptionsNew(opt)/*{{{*/
  {
    setOptions(opt);
    interfaceUpdate();
  };
  /*}}}*/
  function disableCrop()//{{{
  {
    options.disabled = true;
    Selection.disableHandles();
    Selection.setCursor('default');
    Tracker.setCursor('default');
  };
  //}}}
  function enableCrop()//{{{
  {
    options.disabled = false;
    interfaceUpdate();
  };
  //}}}
  function cancelCrop()//{{{
  {
    Selection.done();
    Tracker.activateHandlers(null,null);
  };
  //}}}
  function destroy()//{{{
  {
    $div.remove();
    $origimg.show();
  };
  //}}}

  function interfaceUpdate(alt)//{{{
  // This method tweaks the interface based on options object.
  // Called when options are changed and at end of initialization.
  {
    options.allowResize ?
      alt?Selection.enableOnly():Selection.enableHandles():
      Selection.disableHandles();

    Tracker.setCursor( options.allowSelect? 'crosshair': 'default' );
    Selection.setCursor( options.allowMove? 'move': 'default' );

    $div.css('backgroundColor',options.bgColor);

    if ('setSelect' in options) {
      setSelect(opt.setSelect);
      Selection.done();
      delete(options.setSelect);
    }

    if ('trueSize' in options) {
      xscale = options.trueSize[0] / boundx;
      yscale = options.trueSize[1] / boundy;
    }

    xlimit = options.maxSize[0] || 0;
    ylimit = options.maxSize[1] || 0;
    xmin = options.minSize[0] || 0;
    ymin = options.minSize[1] || 0;

    if ('outerImage' in options)
    {
      $img.attr('src',options.outerImage);
      delete(options.outerImage);
    }

    Selection.refresh();
  };
  //}}}




  //'CHANGE TP ADOPT SINA PS',  START  NEW FUNCTION
  //
  //
  //
  //
  //
  //
  //
  function set_default_lock_ratio_flag(){
    
    
    //alert("crop_param: "+crop_param);
    if ( crop_param_in == "" && thumbnail_fixed_size == 1){
        return 1; //alert("lock ratio = 1 as no crop param");
    }


    var temp_pos = crop_param.split(/x|\+/);
    if (parseInt(100*parseInt(temp_pos[0])/parseInt(temp_pos[1])) ==
      parseInt(100*thumbnail_w/thumbnail_h))
    {
      return 1; //alert("lock ratio = 1 - ratio matched");
    }
    
    //if (thumbnail_fixed_size == 0){
    //  return 0;
    //}
    
    // although thumbnail_fixed_size is fixed, but 
    // crop param not match with current thumbnail aspect ratio.
    // release lock rat
    loosen_lock_ratio = 1;
    return 0; //alert("lock ratio = 0 - ratio match");

  } //
  
  function set_default_zoom_value(){
    if (lock_ratio == 0){
      var temp_pos = crop_param.split(/x|\+/);
      var zoom = thumbnail_w/ parseInt(temp_pos[0]);
      return zoom;
    }  
    
    if (lock_ratio == 1){
      return 1; // its seems it will reclac later.
    } 
  }  


  // set the default crop param, use when the photo is first uploaded
  //   - when first add, it will use mode 1 to upload the photo
  //
  function set_default_crop_param(){
    
    var ar = thumbnail_w/thumbnail_h;
    
    if (thumbnail_fixed_size==1){
      var temp = default_thumbnail_dim.split(/x/);
      ar = parseInt(temp[0])/parseInt(temp[1]);
    } 
    
    
    if (photo_w/photo_h > ar){
      var fw = photo_h*ar;
      var x = (photo_w - fw)/2;     
      return fw+"x"+photo_h+"+"+x+"+0";  // widhtxheight+top_x+top_y
    }

    var fh = photo_w/ar;
    var y = (photo_h - fh)/2;   
    return photo_w+"x"+fh+"+0+"+y;
  }


  // PS require a preview and a few extra field
  //   this function will create all related field and add to the 'main_canvas' div
  //
  function create_ps_working_canvas(){
    var canvas_html  = "<div class=\"jcrop_canvas\"  style=\"text-align: left;  background: #eee; width: 700px; margin: 3.5em auto 2em auto; *margin: 3.5em 10% 2em 10%; border: 1px #333 solid;  padding: 5px;\">";

    //start 'toolbar'
    canvas_html += "<div class=\"toolbar\" style=\"border-bottom:1px solid black; margin-bottom:5px;\">";
    canvas_html += "<div style\"float:left;\" class=\"part1\"><span class=\"zoom\"/></span>";

    if (!crop_param_html_id){
      canvas_html += "Crop param:<input type=\"text\" size=\"12\" class=\"crop_param\" name=\"crop_param\"  />";
    } else {
      canvas_html += "Crop param:<input type=\"text\" size=\"12\" class=\""+crop_param_html_id+"\" name=\""+crop_param_html_id+"\"  />";

    }
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"1:1\" />";

    var panel_lock_ratio_off_default_display = "none";
    var panel_lock_ratio_on_default_display = "inline";

    if (lock_ratio == 0){
      panel_lock_ratio_off_default_display = "inline";
      panel_lock_ratio_on_default_display = "none";
    }


    canvas_html += "<span class=\"panel_lock_ratio_off\" style=\"display:"+panel_lock_ratio_off_default_display+";\">";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"All\" />";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"90%\" />";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"80%\" />";
    canvas_html += "</span>";

    canvas_html += "<span class=\"panel_lock_ratio_on\" style=\"display:"+panel_lock_ratio_on_default_display+";\">";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"Top/Left\" />";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"Center\" />";
    canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"Bottom/Right\" />";
    canvas_html += "</span>";
    
    
    canvas_html += "</div><div style=\"float:right;\" class=\"part2\">";
    if (!thumbnail_html_id){
      canvas_html += "Thumbnail: <input type=\"text\" size=\"6\" class=\"thumbnail\" name=\"thumbnail\" value=\""+thumbnail_dim_in+"\"  />";
    } else {
      canvas_html += "Thumbnail: <input type=\"text\" size=\"6\" class=\""+thumbnail_html_id+"\" name=\""+thumbnail_html_id+"\" value=\""+thumbnail_dim_in+"\"  />";
    }    
    if (lock_ratio == 1){
      canvas_html += "Lock:<input class=\"lock_ratio\" type=\"checkbox\" value=\"1\" checked=\"checked\" />";
    } else {
      canvas_html += "Lock:<input class=\"lock_ratio\" type=\"checkbox\" value=\"1\" />";
    }
    //if (thumbnail_fixed_size==1){
    	canvas_html += "<input class=\"resize_function\" type=\"button\"  value=\"PS Default\" />";
    //}  
    
    canvas_html += "</div><div style=\"clear:both;\"></div>"; //end class=part2
    canvas_html += "</div>";//toolbar

    canvas_html += "<span class=\"debug\"></span>";
    // end thumbnail

    canvas_html += "<div style=\"float:left;\">";
    canvas_html += "<img src=\""+photo+"\" class=\"cropbox\" width=\""+photo_w+"\" height=\""+photo_h+"\" /></div>";
    canvas_html += "<div style=\"float:left;padding:5px;\"><div style=\"overflow: hidden; width: 100px; height: 100px; margin-left: 5px;\" class=\"preview_holder\"><img src=\""+photo+"\" class=\"preview\"></div></div><div style=\"clear:both;\">";

    canvas_html += "</div>";

    $("#"+main_canvas).html(canvas_html);

    $("#"+main_canvas+" .lock_ratio").click( function(){
      
      if (thumbnail_fixed_size==1 && loosen_lock_ratio==0){
      	$("#"+main_canvas+" .lock_ratio").attr("checked",true);
      	alert("Thumbnail size has fixed. Change of aspect ratio is also restricted.");
      	return;
      }	
      
      //if($("#"+main_canvas+" .lock_ratio:checked").val()!= undefined){ // ckecked
      if($("#"+main_canvas+" .lock_ratio:checked").is(':checked')){
        $("#"+main_canvas+" .panel_lock_ratio_off").toggle();
        $("#"+main_canvas+" .panel_lock_ratio_on").toggle();   
        lock_ratio=1;     
      } else {
        $("#"+main_canvas+" .panel_lock_ratio_off").toggle();
        $("#"+main_canvas+" .panel_lock_ratio_on").toggle();
        lock_ratio=0;
      }

    });

    // resize function
    $("#"+main_canvas+" .resize_function").click( function(){
      var resize_type = $(this).val();
      if (resize_type == "1:1"){
        var curr_coord = tellScaled();
        setSelect([curr_coord.x,curr_coord.y,curr_coord.x+thumbnail_w, curr_coord.y+thumbnail_h]);
      } else if (resize_type == "All"){
        set_select_all();
      } else if (resize_type == "90%"){
        set_select_all90();
      } else if (resize_type == "80%"){
        set_select_all80();
      } else if (resize_type == "Center"){
        set_select_center();
      } else if (resize_type == "Top/Left"){
        set_select_top_left();
      } else if (resize_type == "Bottom/Right"){
        set_select_bottom_right();
      } else if (resize_type == "PS Default"){
      	set_default_select_setting();
      }  

      updateCoords( tellScaled() );
    });

     //  onChange event handler for thumbnail field
     var thumbnail_field_selector = get_thumbnail_field_selector();
     //$(thumbnail_field_selector).val("100x50");
     //alert("set "+thumbnail_field_selector);
     $(thumbnail_field_selector).change( function(){     	
       change_thumbnail_size();
     });

    } // end create_ps_working_canvas()


///////////////////////////////////////////////////////////////////
 



  function error_msg(msg){
    $("#"+main_canvas).html(msg);
  }





  // based on the crop_param pass in, set the default section coordinates
  function set_init_selection(crop_param){
      var temp_pos = crop_param.split(/x|\+/);
      var init_x1    = parseInt(temp_pos[2]);
      if (temp_pos[2] == ""){
         init_x1 = (photo_w - thumbnail_w ) /2;
      }
      var init_y1    = parseInt(temp_pos[3]);
      if (temp_pos[3] == ""){
         init_y1 = (photo_h - thumbnail_h ) /2;
      }
      var init_x2    = parseInt(temp_pos[0]) + parseInt(temp_pos[2]);
      if (temp_pos[0] == ""){
         init_x2 = init_x+thumbnail_w;
      }
      var init_y2    = parseInt(temp_pos[1]) + parseInt(temp_pos[3]);
      if (temp_pos[1] == ""){
         init_y2 = init_y+thumbnail_h;
      }
      //alert("init: "+init_x1+" x "+ init_y1 + " + "+ init_x2 + " + "+init_y2);
      return [init_x1, init_y1, init_x2,  init_y2];
    }


  function set_select_all(){
    setSelect([0,0,photo_w, photo_h]);
  }
  function set_select_all90(){
    setSelect([photo_w*0.05,photo_h*0.05,photo_w*0.95, photo_h*0.95]);
  }
  function set_select_all80(){
    setSelect([photo_w*0.1,photo_h*0.1,photo_w*0.9, photo_h*0.9]);
  }

  // set the selection area to 'center' of image
  function set_select_center(){
    var ar = thumbnail_w/thumbnail_h;
    if (photo_w/photo_h > ar){
      var fw = Math.round(photo_h*ar);
      var x = Math.round((photo_w - fw)/2);
      setSelect([x,0,x+fw, photo_h]);
    } else {
      var fh = Math.round(photo_w/ar);
      var y = Math.round((photo_h - fh)/2);
      setSelect([0,y,photo_w, y+fh]);
    }
  }

  function set_select_top_left(){
    var ar = thumbnail_w/thumbnail_h;
    if (photo_w/photo_h > ar){
      var fw = photo_h*ar;
      setSelect([0,0,fw, photo_h]);
    } else {
      var fh = photo_w/ar;
      setSelect([0,0,photo_w, fh]);
    }
  }

  function set_select_bottom_right(){
    var ar = thumbnail_w/thumbnail_h;
    if (photo_w/photo_h > ar){
      var fw = Math.round(photo_h*ar);
      var x = Math.round(photo_w - fw);
      // (top_left_coordinate,  bottom_right_coordinate)
      setSelect([x,0,x+fw, photo_h]);
    } else {
      var fh = Math.round(photo_w/ar);
      var y = Math.round(photo_h - fh);

      setSelect([0,y,photo_w, y+fh]);
    }
  }
  
  function set_default_select_setting(){
  	force_restore_thumbnail_size();
  	
  }

  function force_restore_thumbnail_size(){
   	var thumbnail_field_selector = get_thumbnail_field_selector();
  	  var new_thumbnail_size  = default_thumbnail_dim;
  	  var temp_size = new_thumbnail_size.split(/x/);
      var new_thumbnail_w = thumbnail_w =parseInt(temp_size[0]);
      var new_thumbnail_h = thumbnail_h =parseInt(temp_size[1]);  	  
      
  	  setSelect([0,0,new_thumbnail_w, new_thumbnail_h]);
  	  curr_thumbnail_dim = new_thumbnail_size;
  	  

  	  updateCoords( tellScaled() );
  	  return;
 }

  function change_thumbnail_size(){
  	var thumbnail_field_selector = get_thumbnail_field_selector();
 
  	if (thumbnail_fixed_size == 0 ){// user is allowed to change ratio  		 	
  	  var new_thumbnail_size  = $(thumbnail_field_selector).val();
  	  var temp_size = new_thumbnail_size.split(/x/);
      var new_thumbnail_w = thumbnail_w =parseInt(temp_size[0]);
      var new_thumbnail_h = thumbnail_h =parseInt(temp_size[1]);  	  
      
      options.aspectRatio = new_thumbnail_w / new_thumbnail_h;
  	  setSelect([0,0,new_thumbnail_w, new_thumbnail_h]);
  	  curr_thumbnail_dim = new_thumbnail_size;
  	  

  	  updateCoords( tellScaled() );
  	  return;
  	} 
  	
  	alert("Thumbnail size has fixed\n");
    $(thumbnail_field_selector).val(curr_thumbnail_dim);
  	// user is allowed to change ratio
  		
    	
  }  


  // field to store the thumbnail size
  function get_thumbnail_field_selector(){
     if (!thumbnail_html_id){
       return "#"+main_canvas+" .thumbnail"; //default name
     }
     return  "#"+main_canvas+" ."+thumbnail_html_id;
  }




  // update crop param and zoom.
  function updateCoords(c){
    //alert(c.w+"x"+c.h+"+"+c.x+"+"+c.y);
    if (!crop_param_html_id){ // no custom crop_param field has provided (ps should supply that)
      $("#"+main_canvas+" .crop_param").val(c.w+"x"+c.h+"+"+c.x+"+"+c.y);
    } else {
      $("#"+main_canvas+" ."+crop_param_html_id).val(c.w+"x"+c.h+"+"+c.x+"+"+c.y);
    }

    zoom = thumbnail_w/c.w;
    $("#"+main_canvas+" .zoom").html(parseInt(zoom*100)+'%');

    ps_refresh_thumbnail(c);
  } //method updateCoords

  function ps_refresh_thumbnail(coords){
    if(lock_ratio==1){
      var rx = coords.w != 0 ? thumbnail_w / coords.w : 0;
      var ry = coords.h != 0 ? thumbnail_h / coords.h : 0;

      $("#"+main_canvas+" .preview").css({
        width     : Math.round(rx * photo_w) + 'px',
        Height    : Math.round(ry * photo_h) + 'px',
        marginLeft: '-' + Math.round(rx * coords.x) + 'px',
        marginTop : '-' + Math.round(ry * coords.y) + 'px'
      });
      update_ui(thumbnail_w, thumbnail_h);
      return;
    }

    //only the formula for calcuate the new thumbnail h is different

    var rx = coords.w != 0 ? thumbnail_w / coords.w : 0; //zoom ratio
    var new_thumbnail_h =  Math.round(rx * coords.h);
    var ry = rx;

    $("#"+main_canvas+" .preview").css({
      width     : Math.round(rx * photo_w) + 'px',
      Height    : Math.round(ry * photo_h) + 'px',
      marginLeft: '-' + Math.round(rx * coords.x) + 'px',
      marginTop : '-' + Math.round(ry * coords.y) + 'px'
    });

    update_ui(thumbnail_w, new_thumbnail_h);
    return;

  } // ps_refresh_thumbnail

  
  function update_ui(new_thumbnail_w, new_thumbnail_h){
  	thumbnail_w = new_thumbnail_w;
  	thumbnail_h = new_thumbnail_h;
    $("#"+main_canvas+" .preview_holder").width(new_thumbnail_w);
    $("#"+main_canvas+" .preview_holder").height(new_thumbnail_h);
    var thumbnail_field_selector = get_thumbnail_field_selector();
  	$(thumbnail_field_selector).val(new_thumbnail_w+"x"+new_thumbnail_h);
  	
  	if (lock_ratio == 1){
      options.aspectRatio = new_thumbnail_w / new_thumbnail_h;
    } else {
    	options.aspectRatio = 0;
    }
  }




  //'CHANGE TP ADOPT SINA PS', END



  // }}}

  $hdl_holder.hide();
  interfaceUpdate(true);

  var api = {
    animateTo: animateTo,
    setSelect: setSelect,
    setOptions: setOptionsNew,
    tellSelect: tellSelect,
    tellScaled: tellScaled,

    disable: disableCrop,
    enable: enableCrop,
    cancel: cancelCrop,

    focus: KeyManager.watchKeys,

    getBounds: function() { return [ boundx * xscale, boundy * yscale ]; },
    getWidgetSize: function() { return [ boundx, boundy ]; },

    release: Selection.release,
    destroy: destroy

  };


  //update_aspectRatio();//'CHANGE TP ADOPT SINA PS' //b3
  updateCoords(tellScaled());
  //update_preview();//b3


  $origimg.data('Jcrop',api);
  return api;
};

$.fn.Jcrop = function(options)/*{{{*/
{
  function attachWhenDone(from)/*{{{*/
  {
    var loadsrc = options.useImg || from.src;
    var img = new Image();
    img.onload = function() { $.Jcrop(from,options); };
    img.src = loadsrc;
  };
  /*}}}*/
  if (typeof(options) !== 'object') options = { };

  // Iterate over each object, attach Jcrop
  this.each(function()
  {
    // If we've already attached to this object
    if ($(this).data('Jcrop'))
    {
      // The API can be requested this way (undocumented)
      if (options == 'api') return $(this).data('Jcrop');
      // Otherwise, we just reset the options...
      else $(this).data('Jcrop').setOptions(options);
    }
    // If we haven't been attached, preload and attach
    else attachWhenDone(this);
  });

  // Return "this" so we're chainable a la jQuery plugin-style!
  return this;
};
/*}}}*/

})(jQuery);


